package com.takeoff.iot.modbus.server.message.sender;

import com.ruoyi.common.modbus.factory.*;
import com.ruoyi.common.modbus.message.MiiByteArrayMessage;
import com.ruoyi.common.modbus.message.MiiMessage;
import com.ruoyi.common.modbus.message.factory.MiiMessageFactory;
import com.ruoyi.common.modbus.message.factory.MiiOutMessageFactory;
import com.ruoyi.common.modbus.utils.CacheUtils;
import com.ruoyi.common.modbus.utils.JudgeEmptyUtils;
import com.takeoff.iot.modbus.netty.channel.MiiChannel;
import com.takeoff.iot.modbus.netty.channel.MiiContextChannel;
import org.bouncycastle.util.encoders.Hex;


import lombok.extern.slf4j.Slf4j;

/**
 * 类功能说明：指令下发接口实现<br/>
 * 公司名称：未可自动化 <br/>
 * 作者：weikeauto <br/>
 */
@Slf4j
public class MiiServerMessageSender implements ServerMessageSender {

    private static final MiiBytesFactory<Integer> BYTESFACTORY_SLOT = new MiiSlotBytesFactory();

    private static final MiiMessageFactory<Integer> SINGLE_LOCK = new MiiOutMessageFactory<>(BYTESFACTORY_SLOT);


    private static final MiiBytesFactory<String> BYTESFACTORY_STR = new MiiStrings2BytesFactory();

    private static final MiiMessageFactory<String> SINGLE_STR = new MiiOutMessageFactory<>(BYTESFACTORY_STR);


    public MiiServerMessageSender() {

    }

    private <E> void sendHmMessage(MiiMessageFactory<E> factory, String deviceIp, E... datas) {
        if (JudgeEmptyUtils.isEmpty(CacheUtils.get(deviceIp))) {
            log.info("未找到对应的客户端：" + deviceIp + " 的通讯连接，下发指令失败");
        } else {
            MiiChannel channel = (MiiChannel) CacheUtils.get(deviceIp);
            MiiMessage message = factory.buildMessage(deviceIp, datas);
            log.info("待下发指令数据采集数据：" + channel + "----" + Hex.toHexString(message.toBytes()));
            channel.send(message);
            log.info("下发指令数据结束采集数据：" + Hex.toHexString(message.toBytes()));
        }
    }

    private <E> void sendEditMessage(MiiMessageFactory<E> factory,Integer dataFormat ,String deviceIp, E datas) {
        if (JudgeEmptyUtils.isEmpty(CacheUtils.get(deviceIp))) {
            log.info("未找到对应的客户端：" + deviceIp + " 的通讯连接，下发指令失败");
        } else {
            MiiChannel channel = (MiiChannel) CacheUtils.get(deviceIp);
            MiiMessage message = factory.buildStrMessage(dataFormat,deviceIp, datas);
            log.info("待下发指令数据：" + Hex.toHexString(message.toBytes()));
            channel.send(message);
        }
    }

    private <E> void sendChangeMessage(MiiMessageFactory<E> factory, String deviceIp, E datas) {
        if (JudgeEmptyUtils.isEmpty(CacheUtils.get(deviceIp))) {
            log.info("未找到对应的客户端：" + deviceIp + " 的通讯连接，下发指令失败");
        } else {
            MiiChannel channel = (MiiChannel) CacheUtils.get(deviceIp);
            MiiMessage message = factory.buildChangeMessage(deviceIp, datas);
            log.info("待下发指令数据：" + Hex.toHexString(message.toBytes()));
            channel.send(message);
        }
    }

    private <E> void sendLocationMessage(MiiMessageFactory<E> factory, String deviceIp, E datas) {
        if (JudgeEmptyUtils.isEmpty(CacheUtils.get(deviceIp))) {
            log.info("未找到对应的客户端：" + deviceIp + " 的通讯连接，下发指令失败");
        } else {
            MiiChannel channel = (MiiChannel) CacheUtils.get(deviceIp);
            MiiMessage message = factory.buildLocationMessage(deviceIp, datas);
            log.info("定位待下发指令数据：" + Hex.toHexString(message.toBytes()));
            channel.send(message);
        }
    }

    public static void main(String[] args) {
        System.out.println();
    }



    @Override
    public void testIot(String deviceIp, int device) {
        sendHmMessage(SINGLE_LOCK, deviceIp, device, 0x03, 0x00, 0x00, 0x00, 0x32);
    }

    @Override
    public void closeValve(String deviceIp, int device) {
        sendHmMessage(SINGLE_LOCK, deviceIp, device, 0x06, 0x00, 0x00, 0x00, 0x00);
    }

    @Override
    public void openValve(String deviceIp, int device) {
        sendHmMessage(SINGLE_LOCK, deviceIp, device, 0x06, 0x00, 0x00, 0x00, 0x01);
    }

    @Override
    public void editValve(Integer dataFormat, String sn, int slaveAddress, String position, String data) {
        if (dataFormat == 1) {
            sendEditMessage(SINGLE_STR, dataFormat, sn, "0" + slaveAddress + "06" + position + data);
        }else{
            sendEditMessage(SINGLE_STR, dataFormat, sn, "0" + slaveAddress + "10" + position + "000204" + data);
        }
    }

    @Override
    public void closeValve(int num, String deviceIp, int device) {

        sendChangeMessage(SINGLE_STR, deviceIp, "0106000"+num+"0000");
    }

    @Override
    public void openValve(int num, String deviceIp, int device) {
        sendChangeMessage(SINGLE_STR, deviceIp, "0106000"+num+"0001");
    }

    @Override
    public void testIotLocation(String sn, int device) {
//        if (JudgeEmptyUtils.isEmpty(CacheUtils.get(sn))) {
//            log.info("未找到对应的客户端：" + sn + " 的通讯连接，下发指令失败");
//        } else {
//
//            MiiChannel channel = (MiiChannel) CacheUtils.get(sn);
//            MiiMessage message = SINGLE_STR.buildLocationMessage(sn, datas);
//            log.info("定位待下发指令数据：" + Hex.toHexString(message.toBytes()));
//            channel.send(message);
//        }
        sendLocationMessage(SINGLE_STR, sn, "5745494B4541542B4C42530D0A");
    }


    @Override
    public void passThrough(String sn, byte[] toBytes) {
        if (JudgeEmptyUtils.isEmpty(CacheUtils.get(sn))) {
            log.info("未找到透传对应的客户端：" + sn + " 的通讯连接，下发指令失败");
        } else {
            MiiChannel channel = (MiiChannel) CacheUtils.get(sn);
            MiiMessage message = new MiiByteArrayMessage(sn, toBytes);
            log.info("透传待下发指令数据：" + Hex.toHexString(message.toBytes()));
            channel.send(message);
        }
    }

}
